/*
* Author: Sile Hu
* Created: 2017-03-07
* Description:
* Using the Plexon DO API to control laser, opto, and camera synchronization.
* 
*/

#ifndef __PLEXDOCONTROLLER_H__
#define __PLEXDOCONTROLLER_H__

// HotKeys
#define HighPowerLaserOnKey 'Q'
#define LowPowerLaserOnKey 'W'
#define HighPowerLaserWarmKey 'A'
#define LowPowerLaserWarmKey 'S'
#define StopLaserKey 'Z'
#define StartOptoKey 'O'


// BNC
#define HighPowerLaserChannel 10
#define LowPowerLaserChannel 11
#define CameraAudioPulseChannel 12
#define OptogeneticsLineChannel 2
//#define OptogeneticsLineChannel 1

// DI
#define RecordingTriggerChannel 1
#define HighPowerLaserEventChannel 2

#define LowPowerLaserEventChannel 3
#define ICCameraEventChannel 4
#define CameraAudioEventChannel 5
#define OptoEventChannel 6
#define OptoStartEventChannel 7
#define NoEvent -1

//laser on time
#define LaserOnStimuliTimeMs 6000 //5s
#define LaserOnWarmTimeMs 45000 //45s
//default opto period,duration
#define OptoPulseHighMs 10//5//10 //1s,period,1 Hz
#define OptoPulseLowMs 40//5//40 //1s,period,1 Hz
#define OptoPulseDurationMs 3000 //10s, pulse train duration

typedef struct _DOSTATUS{

	//event channel
	char recTrigChn = RecordingTriggerChannel;
	char HPLaserEvChn = HighPowerLaserEventChannel;
	char LPLaserEvChn = LowPowerLaserEventChannel;
	char ICCamEvChn = ICCameraEventChannel;
	char CamAudioEvChn = CameraAudioEventChannel;
	char OptoEvChn = OptoEventChannel;
	char OptoStEvChn = OptoStartEventChannel;
	
	//device control channel
	char HPLaserChn = HighPowerLaserChannel;
	char LPLaserChn = LowPowerLaserChannel;
	char CamAudioChn = CameraAudioPulseChannel;
	char OptoLineChn = OptogeneticsLineChannel;

	//HotKeys
	char HPLaserOnKey = HighPowerLaserOnKey;
	char LPLaserOnKey = LowPowerLaserOnKey;
	char HPLaserWarmKey = HighPowerLaserWarmKey;
	char LPLaserWarmKey = LowPowerLaserWarmKey;
	char stopLaserKey = StopLaserKey;
	char startOptoKey = StartOptoKey;

	//status
	unsigned int deviceNum = 0;
	bool laserOn = false;
	bool audioPulseOn = false;
	char curChn = 0;
	char curEvChn = 0;
	int curDurTimeMs = 0;
	bool optoOn = false;
	int curOptoPulseHighMs = OptoPulseHighMs;
	int curOptoPulseLowMs = OptoPulseLowMs;
	int curOptoDurationMs = OptoPulseDurationMs;

} DOStatus;

void PlexLaserThread(void* p);
void PlexOptoThread(void* p);
void initPlexDO();
void sendICCaptureEventPulse(int channel, int sleepms = 4);
// not finished yet, should add eventChannel sending code
void generateRandomFreqPulse(int pulseUnitLength_ms, int pulseChannel, int eventChannel);
void KBListener();
void sendLaserOn(int channel, int eventChannel, int ms);
void stopLaserOn();
void sendOptoOn(int highMs, int lowMs, int durationMs);
void PlexSendRecordingStart();

#endif